<?php
// +----------------------------------------------------------------------
// | sfadmin - Suifeng Administration
// +----------------------------------------------------------------------
// | Copyright (c) 2017~2020 http://suifeng.tech All rights reserved.
// +----------------------------------------------------------------------
// | Licensed ( http://www.apache.org/licenses/LICENSE-2.0 )
// +----------------------------------------------------------------------
// | Author: suifeng <1787585212@qq.com>
// +----------------------------------------------------------------------

namespace suifeng\builder\form\control;

use think\Db;
use suifeng\builder\form\Control;
use suifeng\helper\HtmlHelper;

class Select extends Control
{
    /**
     * 选项列表。
     * @var unknown
     */
    public $options;

    /**
     * 初始化默认属性。
     */
    protected function _init_default()
    {
        parent::_init_default();

        if (empty($this->attributes['class'])) {
            $this->attributes['class'] = 'form-control lyui-select select';
        }
    }

    /**
     * 输出HTML。
     *
     * @return string
     */
    protected function _render_core()
    {
        $attributes = $this->attributes;
        $attributes['name'] = $this->_get_formatted_name();

        $html = HtmlHelper::render_start_tag('select', $attributes);
        $html .= $this->_render_options();
        $html .= HtmlHelper::render_end_tag('select');

        return $html;
    }

    /**
     * 输出选项列表。
     *
     * @return string
     */
    protected function _render_options()
    {
        $options = self::parse_options($this->options);

        $html = '';

        $html .= HtmlHelper::render_tag('option', ['value' => ''], '');

        foreach ($options as $value => $title) {
            $attribs = ['value' => $value];
            if ($value == $this->value) {
                $attribs['selected'] = 'selected';
            }
            $html .= HtmlHelper::render_tag('option', $attribs, $title);
        }

        return $html;
    }

    /**
     * 解析选项数组。
     *
     * @return array
     */
    public static function parse_options($options)
    {
        // 如果是数组格式，可以直接使用。
        if (is_array($options)) {
            return $options;
        }

        // options可以以字符串方式定义，形如"prefix:from"。
        // 目前支持如下几种格式：
        // 配置，例如"config:CONFIG_GROUP_LIST"
        // 模型，例如"model:user[fetch_user_select_options]"
        // 数据表，例如"table:user[id,name]"
        // SQL, 例如"sql:select id, nam from admin_user"

        if (strpos($options, ':') !== false) {
            list($prefix, $from) = explode(':', $options);
        } else {
            $prefix = 'config';
            $from = $options;
        }

        switch ($prefix) {
            case 'sql':
                return self::_parse_sql_options($from);

            case 'table':
                return self::_parse_table_options($from);

            case 'model':
                return self::_parse_model_options($from);

            case 'config':
            default:
                return self::_parse_config_options($from);
        }
    }

    private static function _parse_config_options($from)
    {
        $options = config($from);
        return is_array($options) ? $options : [];
    }

    private static function _parse_sql_options($from)
    {
        $rows = Db::query($from);

        $options = [];

        foreach ($rows as $row) {
            $value = array_shift($row);
            $title = $row ? array_shift($row) : $value;
            $options[$value] = $title;
        }

        return $options;
    }

    private static function _parse_table_options($from)
    {
        // 如果$from是字符串，则可以是这样的格式：
        //  table:user[id,name]
        // 如果$from是数组，则可以是下面格式:
        //  [
        //  'table_name'  => 'name',
        //  'where_list'  => [],
        //  'value_field' => 'id',
        //  'title_field' => 'name'
        //  ]

        if (is_array($from)) {
            $table_name = $from['table_name'];
            $where_list = isset($from['where_list']) ? $from['where_list'] : [];
            $value_field = isset($from['value_field']) ? $from['value_field'] : null;
            $title_field = isset($from['title_field']) ? $from['title_field'] : null;
        } else {
            $table_name = substr($from, 0, strpos($from, '['));
            $from = substr($from, strlen($table_name) + 1, strlen($from) - strlen($table_name) - 2);
            list($value_field, $title_field) = explode(',', $from);
            $where_list = [];
        }

        $rows = Db::name($table_name)
            ->where($where_list)
            ->field([$value_field, $title_field])
            ->select();

        $options = [];

        foreach ($rows as $row) {
            $options[$row[$value_field]] = $row[$title_field];
        }

        return $options;
    }

    private static function _parse_model_options($from)
    {
        return [];
    }
}

